<!DOCTYPE html>
<html lang=en>
<head>
    <!-- so meta -->
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="HandheldFriendly" content="True">
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=5" />
    <meta name="description" content="Python Web Flask框架介绍Flask是一个轻量级的基于Python的Web框架。相较于Django，更加轻量便捷，非常适合快速开发 安装1sudo pip install Flask  查看介绍和版本123import flaskprint(flask.__doc__)print(flask.__version__)  Hello World项目结构通过Pycharm新建一个Flas">
<meta property="og:type" content="article">
<meta property="og:title" content="Flask框架快速入门">
<meta property="og:url" content="https://cheung0-bit.github.io/ec225509277f/index.html">
<meta property="og:site_name" content="Bruce Zhang&#39;s Blogs">
<meta property="og:description" content="Python Web Flask框架介绍Flask是一个轻量级的基于Python的Web框架。相较于Django，更加轻量便捷，非常适合快速开发 安装1sudo pip install Flask  查看介绍和版本123import flaskprint(flask.__doc__)print(flask.__version__)  Hello World项目结构通过Pycharm新建一个Flas">
<meta property="og:locale" content="en_US">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706102834115.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706103627152.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706104143150.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706151536714.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706151526649.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706153708150.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706161252973.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220708224340905.png">
<meta property="og:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220708222333577.png">
<meta property="article:published_time" content="2022-07-08T13:34:06.000Z">
<meta property="article:modified_time" content="2022-11-25T07:08:49.931Z">
<meta property="article:author" content="张林">
<meta property="article:tag" content="Flask">
<meta name="twitter:card" content="summary">
<meta name="twitter:image" content="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706102834115.png">
    
    
      
        
          <link rel="shortcut icon" href="/images/favicon.ico">
        
      
      
        
          <link rel="icon" type="image/png" href="/images/favicon-192x192.png" sizes="192x192">
        
      
      
        
          <link rel="apple-touch-icon" sizes="180x180" href="/images/apple-touch-icon.png">
        
      
    
    <!-- title -->
    <title>Flask框架快速入门</title>
    <!-- styles -->
    
<link rel="stylesheet" href="/css/style.css">

    <!-- persian styles -->
    
    <!-- rss -->
    
    
      <link rel="alternate" href="/atom.xml" title="Bruce Zhang&#39;s Blogs" type="application/atom+xml" />
    
	<!-- mathjax -->
	
<meta name="generator" content="Hexo 7.0.0"></head>

<body class="max-width mx-auto px3 ltr">
    
      <div id="header-post">
  <a id="menu-icon" href="#" aria-label="Menu"><i class="fas fa-bars fa-lg"></i></a>
  <a id="menu-icon-tablet" href="#" aria-label="Menu"><i class="fas fa-bars fa-lg"></i></a>
  <a id="top-icon-tablet" href="#" aria-label="Top" onclick="$('html, body').animate({ scrollTop: 0 }, 'fast');" style="display:none;"><i class="fas fa-chevron-up fa-lg"></i></a>
  <span id="menu">
    <span id="nav">
      <ul>
        <!--
       --><li><a href="/">Home</a></li><!--
     --><!--
       --><li><a href="/about/">About</a></li><!--
     --><!--
       --><li><a href="/archives/">Articles</a></li><!--
     --><!--
       --><li><a href="/categories/">Category</a></li><!--
     --><!--
       --><li><a href="/search/">Search</a></li><!--
     -->
      </ul>
    </span>
    <br/>
    <span id="actions">
      <ul>
        
        <li><a class="icon" aria-label="Previous post" href="/ab96bd0fdf5d/"><i class="fas fa-chevron-left" aria-hidden="true" onmouseover="$('#i-prev').toggle();" onmouseout="$('#i-prev').toggle();"></i></a></li>
        
        
        <li><a class="icon" aria-label="Next post" href="/f36f3cc3c14e/"><i class="fas fa-chevron-right" aria-hidden="true" onmouseover="$('#i-next').toggle();" onmouseout="$('#i-next').toggle();"></i></a></li>
        
        <li><a class="icon" aria-label="Back to top" href="#" onclick="$('html, body').animate({ scrollTop: 0 }, 'fast');"><i class="fas fa-chevron-up" aria-hidden="true" onmouseover="$('#i-top').toggle();" onmouseout="$('#i-top').toggle();"></i></a></li>
        <li><a class="icon" aria-label="Share post" href="#"><i class="fas fa-share-alt" aria-hidden="true" onmouseover="$('#i-share').toggle();" onmouseout="$('#i-share').toggle();" onclick="$('#share').toggle();return false;"></i></a></li>
      </ul>
      <span id="i-prev" class="info" style="display:none;">Previous post</span>
      <span id="i-next" class="info" style="display:none;">Next post</span>
      <span id="i-top" class="info" style="display:none;">Back to top</span>
      <span id="i-share" class="info" style="display:none;">Share post</span>
    </span>
    <br/>
    <div id="share" style="display: none">
      <ul>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.facebook.com/sharer.php?u=https://cheung0-bit.github.io/ec225509277f/"><i class="fab fa-facebook " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://twitter.com/share?url=https://cheung0-bit.github.io/ec225509277f/&text=Flask框架快速入门"><i class="fab fa-twitter " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.linkedin.com/shareArticle?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-linkedin " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://pinterest.com/pin/create/bookmarklet/?url=https://cheung0-bit.github.io/ec225509277f/&is_video=false&description=Flask框架快速入门"><i class="fab fa-pinterest " aria-hidden="true"></i></a></li>
  <li><a class="icon" href="mailto:?subject=Flask框架快速入门&body=Check out this article: https://cheung0-bit.github.io/ec225509277f/"><i class="fas fa-envelope " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://getpocket.com/save?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-get-pocket " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://reddit.com/submit?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-reddit " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.stumbleupon.com/submit?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-stumbleupon " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://digg.com/submit?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-digg " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.tumblr.com/share/link?url=https://cheung0-bit.github.io/ec225509277f/&name=Flask框架快速入门&description="><i class="fab fa-tumblr " aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://news.ycombinator.com/submitlink?u=https://cheung0-bit.github.io/ec225509277f/&t=Flask框架快速入门"><i class="fab fa-hacker-news " aria-hidden="true"></i></a></li>
</ul>

    </div>
    <div id="toc">
      <ol class="toc"><li class="toc-item toc-level-1"><a class="toc-link" href="#Python-Web-Flask%E6%A1%86%E6%9E%B6"><span class="toc-number">1.</span> <span class="toc-text">Python Web Flask框架</span></a><ol class="toc-child"><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BB%8B%E7%BB%8D"><span class="toc-number">1.1.</span> <span class="toc-text">介绍</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%AE%89%E8%A3%85"><span class="toc-number">1.2.</span> <span class="toc-text">安装</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%9F%A5%E7%9C%8B%E4%BB%8B%E7%BB%8D%E5%92%8C%E7%89%88%E6%9C%AC"><span class="toc-number">1.2.1.</span> <span class="toc-text">查看介绍和版本</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#Hello-World"><span class="toc-number">1.3.</span> <span class="toc-text">Hello World</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E9%A1%B9%E7%9B%AE%E7%BB%93%E6%9E%84"><span class="toc-number">1.3.1.</span> <span class="toc-text">项目结构</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%AC%AC%E4%B8%80%E4%B8%AA%E7%A8%8B%E5%BA%8F"><span class="toc-number">1.3.2.</span> <span class="toc-text">第一个程序</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E4%BF%AE%E6%94%B9Flask%E9%85%8D%E7%BD%AE"><span class="toc-number">1.3.3.</span> <span class="toc-text">修改Flask配置</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Debug%E6%A8%A1%E5%BC%8F"><span class="toc-number">1.3.4.</span> <span class="toc-text">Debug模式</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%BB%91%E5%AE%9AIP%E5%92%8C%E7%AB%AF%E5%8F%A3"><span class="toc-number">1.3.5.</span> <span class="toc-text">绑定IP和端口</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%8E%B7%E5%8F%96URL%E5%8F%82%E6%95%B0"><span class="toc-number">1.4.</span> <span class="toc-text">获取URL参数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%8E%B7%E5%8F%96POST%E5%8F%82%E6%95%B0"><span class="toc-number">1.5.</span> <span class="toc-text">获取POST参数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%A7%A3%E6%9E%90JSON"><span class="toc-number">1.6.</span> <span class="toc-text">解析JSON</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%BF%94%E5%9B%9E%E4%BD%93%E8%87%AA%E5%AE%9A%E4%B9%89"><span class="toc-number">1.6.1.</span> <span class="toc-text">返回体自定义</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%96%B9%E5%BC%8F%E4%B8%80"><span class="toc-number">1.6.1.1.</span> <span class="toc-text">方式一</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%96%B9%E5%BC%8F%E4%BA%8C"><span class="toc-number">1.6.1.2.</span> <span class="toc-text">方式二</span></a></li></ol></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%B8%8A%E4%BC%A0%E6%96%87%E4%BB%B6"><span class="toc-number">1.7.</span> <span class="toc-text">上传文件</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#RESTFUL%E9%A3%8E%E6%A0%BCURL"><span class="toc-number">1.8.</span> <span class="toc-text">RESTFUL风格URL</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%88%9D%E6%8E%A2"><span class="toc-number">1.8.1.</span> <span class="toc-text">初探</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%B1%BB%E5%9E%8B%E8%BD%AC%E6%8D%A2"><span class="toc-number">1.8.2.</span> <span class="toc-text">类型转换</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E4%BD%BF%E7%94%A8url-for"><span class="toc-number">1.8.3.</span> <span class="toc-text">使用url_for</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#redirect%E9%87%8D%E5%AE%9A%E5%90%91"><span class="toc-number">1.9.</span> <span class="toc-text">redirect重定向</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BD%BF%E7%94%A8jinja2%E6%A8%A1%E6%9D%BF%E5%BC%95%E6%93%8E"><span class="toc-number">1.10.</span> <span class="toc-text">使用jinja2模板引擎</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%BF%9E%E6%8E%A5%E6%95%B0%E6%8D%AE%E5%BA%93"><span class="toc-number">1.11.</span> <span class="toc-text">连接数据库</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E5%85%A5%E5%BA%93"><span class="toc-number">1.11.1.</span> <span class="toc-text">引入库</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%A7%84%E8%8C%83%E4%B8%80%E4%B8%AA%E6%95%B0%E6%8D%AE%E5%BA%93%E6%93%8D%E4%BD%9C%E7%B1%BB%EF%BC%88%E4%BB%A5MySQL%E4%B8%BA%E4%BE%8B%EF%BC%89"><span class="toc-number">1.11.2.</span> <span class="toc-text">规范一个数据库操作类（以MySQL为例）</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AE%9E%E4%BE%8B%E5%8C%96%E4%B8%80%E4%B8%AA%E5%85%A8%E5%B1%80%E5%8D%95%E4%BE%8B"><span class="toc-number">1.11.3.</span> <span class="toc-text">实例化一个全局单例</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%85%A8%E5%B1%80%E4%BD%BF%E7%94%A8"><span class="toc-number">1.11.4.</span> <span class="toc-text">全局使用</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%87%AA%E5%AE%9A%E4%B9%89%E8%A3%85%E9%A5%B0%E5%99%A8"><span class="toc-number">1.12.</span> <span class="toc-text">自定义装饰器</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AF%BC%E5%8C%85"><span class="toc-number">1.12.1.</span> <span class="toc-text">导包</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%87%AA%E5%AE%9A%E4%B9%89%E5%A4%84%E7%90%86%E9%80%BB%E8%BE%91"><span class="toc-number">1.12.2.</span> <span class="toc-text">自定义处理逻辑</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%83%BD%E5%81%9A%E4%BA%9B%E4%BB%80%E4%B9%88"><span class="toc-number">1.12.3.</span> <span class="toc-text">能做些什么</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E9%85%8D%E7%BD%AESwagger%E6%96%87%E6%A1%A3"><span class="toc-number">1.13.</span> <span class="toc-text">配置Swagger文档</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E5%85%A5%E5%BA%93-1"><span class="toc-number">1.13.1.</span> <span class="toc-text">引入库</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E9%85%8D%E7%BD%AE%E7%9B%B8%E5%85%B3%E4%BF%A1%E6%81%AF"><span class="toc-number">1.13.2.</span> <span class="toc-text">配置相关信息</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AF%B9%E5%BA%94%E6%AF%8F%E4%B8%80%E4%B8%AA%E6%8E%A5%E5%8F%A3%E5%A1%AB%E5%86%99%E6%8F%8F%E8%BF%B0%E4%BF%A1%E6%81%AF"><span class="toc-number">1.13.3.</span> <span class="toc-text">对应每一个接口填写描述信息</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%9C%9F%E5%AE%9E%E7%9A%84%E6%A0%B7%E8%B2%8C"><span class="toc-number">1.13.4.</span> <span class="toc-text">真实的样貌</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%BC%80%E5%90%AF%E8%B7%A8%E5%9F%9F"><span class="toc-number">1.14.</span> <span class="toc-text">开启跨域</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E5%85%A5%E5%BA%93-2"><span class="toc-number">1.14.1.</span> <span class="toc-text">引入库</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%B8%B8%E7%94%A8%E9%85%8D%E7%BD%AE"><span class="toc-number">1.14.2.</span> <span class="toc-text">常用配置</span></a></li></ol></li></ol></li></ol>
    </div>
  </span>
</div>

    
    <div class="content index py4">
        
        <article class="post" itemscope itemtype="http://schema.org/BlogPosting">
  <header>
    
    <h1 class="posttitle" itemprop="name headline">
        Flask框架快速入门
    </h1>



    <div class="meta">
      <span class="author" itemprop="author" itemscope itemtype="http://schema.org/Person">
        <span itemprop="name">张林</span>
      </span>
      
    <div class="postdate">
      
        <time datetime="2022-07-08T13:34:06.000Z" itemprop="datePublished">2022-07-08</time>
        
        (Updated: <time datetime="2022-11-25T07:08:49.931Z" itemprop="dateModified">2022-11-25</time>)
        
      
    </div>


      
    <div class="article-category">
        <i class="fas fa-archive"></i>
        <a class="category-link" href="/categories/Python/">Python</a>
    </div>


      
    <div class="article-tag">
        <i class="fas fa-tag"></i>
        <a class="tag-link-link" href="/tags/Flask/" rel="tag">Flask</a>
    </div>


    </div>
  </header>
  

  <div class="content" itemprop="articleBody">
    <h1 id="Python-Web-Flask框架"><a href="#Python-Web-Flask框架" class="headerlink" title="Python Web Flask框架"></a>Python Web Flask框架</h1><h2 id="介绍"><a href="#介绍" class="headerlink" title="介绍"></a>介绍</h2><p>Flask是一个轻量级的基于Python的Web框架。相较于Django，更加轻量便捷，非常适合快速开发</p>
<h2 id="安装"><a href="#安装" class="headerlink" title="安装"></a>安装</h2><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">sudo pip install Flask</span><br></pre></td></tr></table></figure>

<h3 id="查看介绍和版本"><a href="#查看介绍和版本" class="headerlink" title="查看介绍和版本"></a>查看介绍和版本</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> flask</span><br><span class="line"><span class="built_in">print</span>(flask.__doc__)</span><br><span class="line"><span class="built_in">print</span>(flask.__version__)</span><br></pre></td></tr></table></figure>

<h2 id="Hello-World"><a href="#Hello-World" class="headerlink" title="Hello World"></a>Hello World</h2><h3 id="项目结构"><a href="#项目结构" class="headerlink" title="项目结构"></a>项目结构</h3><p>通过Pycharm新建一个Flask项目，可以看到初始化的目录结构为：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">├─app.py</span><br><span class="line">├─static</span><br><span class="line">└─templates</span><br></pre></td></tr></table></figure>

<ul>
<li><p>static用于放置静态资源</p>
</li>
<li><p>templates存放模板文件</p>
</li>
<li><p>app.py是程序启动文件</p>
</li>
</ul>
<h3 id="第一个程序"><a href="#第一个程序" class="headerlink" title="第一个程序"></a>第一个程序</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">hello_world</span>():  <span class="comment"># put application&#x27;s code here</span></span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;Hello World!&#x27;</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run()</span><br></pre></td></tr></table></figure>

<p>运行结果：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">FLASK_APP = app.py</span><br><span class="line">FLASK_ENV = development</span><br><span class="line">FLASK_DEBUG = 0</span><br><span class="line">In folder C:/Users/Lin/Desktop/project/flask</span><br><span class="line"><span class="string">&quot;C:\Program Files\Python39\python.exe&quot;</span> -m flask run</span><br><span class="line"> * Serving Flask app <span class="string">&#x27;app.py&#x27;</span> (lazy loading)</span><br><span class="line"> * Environment: development</span><br><span class="line"> * Debug mode: off</span><br><span class="line"> * Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)</span><br><span class="line">127.0.0.1 - - [05/Jul/2022 20:39:10] <span class="string">&quot;GET / HTTP/1.1&quot;</span> 200 -</span><br><span class="line">127.0.0.1 - - [05/Jul/2022 20:39:10] <span class="string">&quot;GET /favicon.ico HTTP/1.1&quot;</span> 404 -</span><br></pre></td></tr></table></figure>

<p>浏览器访问<a target="_blank" rel="noopener" href="http://127.0.0.1:5000/%E5%B0%B1%E4%BC%9A%E6%98%BE%E7%A4%BAHello">http://127.0.0.1:5000/就会显示Hello</a> World</p>
<p>终端也会记录下访问的日志</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">127.0.0.1 - - [05/Jul/2022 20:39:10] <span class="string">&quot;GET / HTTP/1.1&quot;</span> 200 -</span><br></pre></td></tr></table></figure>

<h3 id="修改Flask配置"><a href="#修改Flask配置" class="headerlink" title="修改Flask配置"></a>修改Flask配置</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">app = Flask(__name__)</span><br></pre></td></tr></table></figure>

<p>其中，<code>__name__</code>为默认值<code>__main__</code>。可以将这个参数自定义为自己的项目名。也可以自定义静态资源、模板文件文件夹：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">app = Flask(<span class="string">&#x27;my-project&#x27;</span>, static_folder=<span class="string">&#x27;my-static&#x27;</span>, template_folder=<span class="string">&#x27;my-template&#x27;</span>)</span><br></pre></td></tr></table></figure>

<p>更多自定义参数可以进入源码查看</p>
<h3 id="Debug模式"><a href="#Debug模式" class="headerlink" title="Debug模式"></a>Debug模式</h3><p>默认情况下，程序运行不会开启debug模式。此时，服务端出现错误信息不会在客户端显示。在开发过程中，查看错误信息是非常很有必要的，因此我们打开debug模式：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">app.run(debug=<span class="literal">True</span>)</span><br></pre></td></tr></table></figure>

<p>另外，会触发热重载</p>
<h3 id="绑定IP和端口"><a href="#绑定IP和端口" class="headerlink" title="绑定IP和端口"></a>绑定IP和端口</h3><p>Flask默认只能通过本机也就是<code>127.0.0.1</code>访问，默认端口为<code>5000</code>.</p>
<p>我们可以自定义：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">8080</span>, debug=<span class="literal">True</span>) <span class="comment"># 0.0.0.0 代表所有网卡可以访问</span></span><br></pre></td></tr></table></figure>

<h2 id="获取URL参数"><a href="#获取URL参数" class="headerlink" title="获取URL参数"></a>获取URL参数</h2><p>URL参数即出现在url中的键值对，例如<a target="_blank" rel="noopener" href="http://127.0.0.1/?username=jay-chou&password=123456">http://127.0.0.1?username=jay-chou&amp;password=123456</a></p>
<p>则此时的参数是</p>
<figure class="highlight json"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="punctuation">&#123;</span></span><br><span class="line">    &#x27;username&#x27;<span class="punctuation">:</span>&#x27;jay-chou&#x27;<span class="punctuation">,</span></span><br><span class="line">    &#x27;password&#x27;<span class="punctuation">:</span>&#x27;<span class="number">123456</span>&#x27;</span><br><span class="line"><span class="punctuation">&#125;</span></span><br></pre></td></tr></table></figure>

<p>可以通过以下示例程序查看</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">hello_world</span>():</span><br><span class="line">    <span class="keyword">return</span> request.args.__str__()</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<p>则会在网页上显示</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">ImmutableMultiDict([(<span class="string">&#x27;username&#x27;</span>, <span class="string">&#x27;jay-chou&#x27;</span>), (<span class="string">&#x27;password&#x27;</span>, <span class="string">&#x27;123456&#x27;</span>)])</span><br></pre></td></tr></table></figure>

<p><code>request</code>方法还有多个API，这里简单罗列一下</p>
<p>可以通过一下程序进行测试体会</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> importlib.resources <span class="keyword">import</span> path</span><br><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request</span><br><span class="line"><span class="keyword">from</span> sympy <span class="keyword">import</span> re</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">hello_world</span>():</span><br><span class="line">    path = request.path  <span class="comment"># 获取装饰器下的路径</span></span><br><span class="line">    full_path = request.full_path  <span class="comment"># 获取完整路径带上参数信息</span></span><br><span class="line">    username = request.args.get(<span class="string">&#x27;username&#x27;</span>)  <span class="comment"># 获取指定键值</span></span><br><span class="line">    <span class="comment"># 同上 第二个参数表示默认值，当第一个参数获取的值为None时，则取默认值</span></span><br><span class="line">    password = request.args.get(<span class="string">&#x27;password&#x27;</span>, <span class="string">&#x27;default&#x27;</span>)</span><br><span class="line">    <span class="built_in">list</span> = request.args.getlist(<span class="string">&#x27;p&#x27;</span>)  <span class="comment"># 获取同一个键的所有值，以列表的方式存下来</span></span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;===================&#x27;</span>)</span><br><span class="line">    <span class="built_in">print</span>(path)</span><br><span class="line">    <span class="built_in">print</span>(full_path)</span><br><span class="line">    <span class="built_in">print</span>(username)</span><br><span class="line">    <span class="built_in">print</span>(password)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">list</span>)</span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;===================&#x27;</span>)</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;OK&#x27;</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br></pre></td></tr></table></figure>

<p>控制台输出结果：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">===================</span><br><span class="line">/</span><br><span class="line">/?username=jay-chou&amp;p=1&amp;p=2</span><br><span class="line">jay-chou</span><br><span class="line">default</span><br><span class="line">[<span class="string">&#x27;1&#x27;</span>, <span class="string">&#x27;2&#x27;</span>]</span><br><span class="line">===================</span><br></pre></td></tr></table></figure>

<h2 id="获取POST参数"><a href="#获取POST参数" class="headerlink" title="获取POST参数"></a>获取POST参数</h2><p>在实际开发中，我们遵行RESTFUL风格，一般数据都通过表单提交，使用POST请求，一下示例程序将简单展示如何获取POST表单</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/login&#x27;</span>, methods=[<span class="string">&#x27;POST&#x27;</span>]</span>) </span><span class="comment"># 限制只能通过POST请求来访问该API</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">login</span>():</span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;=============================&#x27;</span>)</span><br><span class="line">    <span class="built_in">print</span>(request.headers)  <span class="comment"># 获取HTTP请求头</span></span><br><span class="line">    <span class="built_in">print</span>(request.stream.read())  <span class="comment"># 流式读取请求数据</span></span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;=============================&#x27;</span>)</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;OK&#x27;</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<p>这里我使用<code>ApiFox</code>进行测试：</p>
<p><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706102834115.png" alt="image-20220706102834115"></p>
<p>控制台打印结果：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line">=============================</span><br><span class="line">User-Agent: apifox/1.0.0 (https://www.apifox.cn)      </span><br><span class="line">Content-Type: application/json</span><br><span class="line">Accept: */*</span><br><span class="line">Host: 127.0.0.1</span><br><span class="line">Accept-Encoding: gzip, deflate, br</span><br><span class="line">Connection: keep-alive</span><br><span class="line">Content-Length: 57</span><br><span class="line"></span><br><span class="line"></span><br><span class="line">b<span class="string">&#x27;&#123;\r\n    &quot;username&quot;:&quot;Jay-Chou&quot;,\r\n    &quot;password&quot;:&quot;123456&quot;\r\n&#125;&#x27;</span></span><br><span class="line">=============================</span><br></pre></td></tr></table></figure>

<p>可以看到我们获取到的是二进制数据，此时，我们可以使用Flask自带的表单解析API</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/login&#x27;</span>, methods=[<span class="string">&#x27;POST&#x27;</span>]</span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">login</span>():</span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;=============================&#x27;</span>)</span><br><span class="line">    <span class="built_in">print</span>(request.headers)</span><br><span class="line">    <span class="built_in">print</span>(request.form)</span><br><span class="line">    <span class="built_in">print</span>(request.form[<span class="string">&#x27;username&#x27;</span>])</span><br><span class="line">    <span class="built_in">print</span>(request.form[<span class="string">&#x27;password&#x27;</span>])</span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;=============================&#x27;</span>)</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;OK&#x27;</span></span><br></pre></td></tr></table></figure>

<p><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706103627152.png" alt="image-20220706103627152"></p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">=============================</span><br><span class="line">User-Agent: apifox/1.0.0 (https://www.apifox.cn)      </span><br><span class="line">Accept: */*</span><br><span class="line">Host: 127.0.0.1</span><br><span class="line">Accept-Encoding: gzip, deflate, br</span><br><span class="line">Connection: keep-alive</span><br><span class="line">Content-Type: application/x-www-form-urlencoded       </span><br><span class="line">Content-Length: 33</span><br><span class="line"></span><br><span class="line"></span><br><span class="line">ImmutableMultiDict([(<span class="string">&#x27;username&#x27;</span>, <span class="string">&#x27;Jay-Chou&#x27;</span>), (<span class="string">&#x27;password&#x27;</span>, <span class="string">&#x27;123456&#x27;</span>)])</span><br><span class="line">Jay-Chou</span><br><span class="line">123456</span><br><span class="line">=============================</span><br></pre></td></tr></table></figure>

<p>注意此时<code>Content-Type</code>为<code>application/x-www-form-urlencoded</code></p>
<h2 id="解析JSON"><a href="#解析JSON" class="headerlink" title="解析JSON"></a>解析JSON</h2><p>大多数情况下，前后端交互都是通过JSON的方式，<code>Content-Type</code>此时为<code>application/json</code>， 那么我们应该将其解析成对应的Python类型</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/login&#x27;</span>, methods=[<span class="string">&#x27;POST&#x27;</span>]</span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">login</span>():</span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;=============================&#x27;</span>)</span><br><span class="line">    <span class="built_in">print</span>(request.headers)</span><br><span class="line">    <span class="built_in">print</span>(request.json)</span><br><span class="line">    <span class="built_in">print</span>(request.json[<span class="string">&#x27;username&#x27;</span>])</span><br><span class="line">    <span class="built_in">print</span>(request.json[<span class="string">&#x27;password&#x27;</span>])</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(request.json))</span><br><span class="line">    <span class="built_in">print</span>(<span class="string">&#x27;=============================&#x27;</span>)</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;OK&#x27;</span></span><br></pre></td></tr></table></figure>

<p><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706104143150.png" alt="image-20220706104143150"></p>
<p>控制台打印结果：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line">=============================</span><br><span class="line">User-Agent: apifox/1.0.0 (https://www.apifox.cn)      </span><br><span class="line">Content-Type: application/json</span><br><span class="line">Accept: */*</span><br><span class="line">Host: 127.0.0.1</span><br><span class="line">Accept-Encoding: gzip, deflate, br</span><br><span class="line">Connection: keep-alive</span><br><span class="line">Content-Length: 57</span><br><span class="line"></span><br><span class="line"></span><br><span class="line">&#123;<span class="string">&#x27;username&#x27;</span>: <span class="string">&#x27;Jay-Chou&#x27;</span>, <span class="string">&#x27;password&#x27;</span>: <span class="string">&#x27;123456&#x27;</span>&#125;        </span><br><span class="line">Jay-Chou</span><br><span class="line">123456</span><br><span class="line">&lt;class <span class="string">&#x27;dict&#x27;</span>&gt;</span><br><span class="line">=============================</span><br></pre></td></tr></table></figure>

<h3 id="返回体自定义"><a href="#返回体自定义" class="headerlink" title="返回体自定义"></a>返回体自定义</h3><h4 id="方式一"><a href="#方式一" class="headerlink" title="方式一"></a>方式一</h4><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/login&#x27;</span>, methods=[<span class="string">&#x27;POST&#x27;</span>]</span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">login</span>():</span><br><span class="line">    res = request.json</span><br><span class="line">    <span class="comment"># 方式一</span></span><br><span class="line">    resp = Response(json.dumps(res), mimetype=<span class="string">&#x27;application/json&#x27;</span>)</span><br><span class="line">    <span class="keyword">return</span> resp</span><br></pre></td></tr></table></figure>

<h4 id="方式二"><a href="#方式二" class="headerlink" title="方式二"></a>方式二</h4><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/login&#x27;</span>, methods=[<span class="string">&#x27;POST&#x27;</span>]</span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">login</span>():</span><br><span class="line">    res = request.json</span><br><span class="line">    <span class="comment"># 方式一</span></span><br><span class="line">    resp = jsonify(res)</span><br><span class="line">    <span class="keyword">return</span> resp</span><br></pre></td></tr></table></figure>

<p>均会得到返回结果：</p>
<figure class="highlight json"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="punctuation">&#123;</span></span><br><span class="line">    <span class="attr">&quot;password&quot;</span><span class="punctuation">:</span> <span class="string">&quot;123456&quot;</span><span class="punctuation">,</span></span><br><span class="line">    <span class="attr">&quot;username&quot;</span><span class="punctuation">:</span> <span class="string">&quot;Jay-Chou&quot;</span></span><br><span class="line"><span class="punctuation">&#125;</span></span><br></pre></td></tr></table></figure>

<h2 id="上传文件"><a href="#上传文件" class="headerlink" title="上传文件"></a>上传文件</h2><p>上传文件也是使用POST方法，这里我们将上传的文件放在<code>static</code>目录下</p>
<p>示例程序</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> uuid <span class="keyword">import</span> uuid1</span><br><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request</span><br><span class="line"><span class="keyword">import</span> os</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"><span class="comment"># 文件上传目录</span></span><br><span class="line">app.config[<span class="string">&#x27;UPLOAD_FOLDER&#x27;</span>] = <span class="string">&#x27;static&#x27;</span></span><br><span class="line"><span class="comment"># 支持的文件格式</span></span><br><span class="line">app.config[<span class="string">&#x27;ALLOW_EXTENSIONS&#x27;</span>] = &#123;<span class="string">&#x27;png&#x27;</span>, <span class="string">&#x27;jpg&#x27;</span>, <span class="string">&#x27;jpeg&#x27;</span>, <span class="string">&#x27;gif&#x27;</span>&#125;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">isAllowed</span>(<span class="params">filename</span>):  <span class="comment"># 判断是否为指定格式</span></span><br><span class="line">    <span class="comment"># rsplit方法表示从字符串后面开始分割，第二个参数表示分割次数</span></span><br><span class="line">    <span class="comment"># 例如：xxx.png.jpg 会被分割为 [&#x27;xxx.png&#x27;,&#x27;jpg&#x27;]</span></span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;.&#x27;</span> <span class="keyword">in</span> filename <span class="keyword">and</span> \</span><br><span class="line">        filename.rsplit(<span class="string">&#x27;.&#x27;</span>, <span class="number">1</span>)[<span class="number">1</span>] <span class="keyword">in</span> app.config[<span class="string">&#x27;ALLOW_EXTENSIONS&#x27;</span>]</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">generateName</span>(<span class="params">filename</span>):</span><br><span class="line">    <span class="keyword">return</span> <span class="built_in">str</span>(uuid1()) + <span class="string">&#x27;.&#x27;</span> + filename.rsplit(<span class="string">&#x27;.&#x27;</span>, <span class="number">1</span>)[<span class="number">1</span>]</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/upload&#x27;</span>, methods=[<span class="string">&#x27;POST&#x27;</span>]</span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">upload</span>():</span><br><span class="line">    <span class="keyword">try</span>:</span><br><span class="line">        image = request.files[<span class="string">&#x27;image&#x27;</span>]</span><br><span class="line">        <span class="keyword">if</span> image <span class="keyword">and</span> isAllowed(image.filename):</span><br><span class="line">            <span class="comment"># 使用自定义文件名保存图片（这里采用UUID）</span></span><br><span class="line">            filename = generateName(image.filename)</span><br><span class="line">            path = os.path.join(app.config[<span class="string">&#x27;UPLOAD_FOLDER&#x27;</span>], filename)</span><br><span class="line">            <span class="built_in">print</span>(path)</span><br><span class="line">            image.save(path)</span><br><span class="line">            <span class="keyword">return</span> <span class="string">&#x27;success&#x27;</span></span><br><span class="line">        <span class="keyword">else</span>:</span><br><span class="line">            <span class="keyword">return</span> <span class="string">&#x27;fail&#x27;</span></span><br><span class="line">    <span class="keyword">except</span> Exception <span class="keyword">as</span> e:</span><br><span class="line">        <span class="built_in">print</span>(e)</span><br><span class="line">        <span class="keyword">return</span> <span class="built_in">str</span>(e)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<p>使用<code>ApiFox</code>进行测试：<br><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706151536714.png" alt="image-20220706151536714"><br><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706151526649.png" alt="image-20220706151526649"></p>
<h2 id="RESTFUL风格URL"><a href="#RESTFUL风格URL" class="headerlink" title="RESTFUL风格URL"></a>RESTFUL风格URL</h2><h3 id="初探"><a href="#初探" class="headerlink" title="初探"></a>初探</h3><p>采用restful风格的url可以取代原始的方式</p>
<p>下面是示例程序：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/user/&lt;username&gt;&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryUser</span>(<span class="params">username</span>):</span><br><span class="line">    <span class="built_in">print</span>(username)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(username))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;welcome &#x27;</span> + username</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/user/&lt;username&gt;/all&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryAllUsers</span>(<span class="params">username</span>):</span><br><span class="line">    <span class="built_in">print</span>(username)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(username))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;welcome &#x27;</span> + username</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<ul>
<li><p>访问<a target="_blank" rel="noopener" href="http://127.0.0.1/user/jay-chou">http://127.0.0.1/user/jay-chou</a></p>
<ul>
<li>返回welcome jay-chou</li>
<li>打印</li>
</ul>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">jay-chou</span><br><span class="line">&lt;class <span class="string">&#x27;str&#x27;</span>&gt;</span><br></pre></td></tr></table></figure>
</li>
<li><p>访问<a target="_blank" rel="noopener" href="http://127.0.0.1/user/jay-chou/">http://127.0.0.1/user/jay-chou/</a></p>
<ul>
<li>返回Not Found</li>
</ul>
</li>
<li><p>访问<a target="_blank" rel="noopener" href="http://127.0.0.1/user/jay-chou//all">http://127.0.0.1/user/jay-chou//all</a></p>
<ul>
<li>返回welcome jay-chou</li>
<li>打印</li>
</ul>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">jay-chou</span><br><span class="line">&lt;class <span class="string">&#x27;str&#x27;</span>&gt;</span><br></pre></td></tr></table></figure>

<p>由此可以看出，传递的都是str类型的变量，且url必须完整</p>
</li>
</ul>
<h3 id="类型转换"><a href="#类型转换" class="headerlink" title="类型转换"></a>类型转换</h3><p>如果需求是根据用户ID查询，那么我们就要拿到一个数字类型的变量，此时可以这么做：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/user/queryById/&lt;int:num&gt;&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryUserById</span>(<span class="params">num</span>):</span><br><span class="line">    <span class="built_in">print</span>(num)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(num))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;查询成功&#x27;</span></span><br></pre></td></tr></table></figure>

<p>若访问<a target="_blank" rel="noopener" href="http://127.0.0.1/user/queryById/1">http://127.0.0.1/user/queryById/1</a></p>
<p>则会返回<code>查询成功</code>，打印</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">1</span><br><span class="line">&lt;class <span class="string">&#x27;int&#x27;</span>&gt;</span><br></pre></td></tr></table></figure>

<p>若url中不是一个数字，则会返回Not Found<br><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706153708150.png" alt="image-20220706153708150"></p>
<p>Flask自带的转换器类型：</p>
<ul>
<li>int 接受整数</li>
<li>float 接受浮点数</li>
<li>string 默认是字符串接收器</li>
<li>path 和默认相似 但也接受斜线</li>
</ul>
<p>此外，可以自定义转换器用于校验，这里就不多赘述了</p>
<h3 id="使用url-for"><a href="#使用url-for" class="headerlink" title="使用url_for"></a>使用url_for</h3><p>工具函数<code>url_for</code>可以让你以软编码的形式生成url，提供开发效率</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request, url_for</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/user/&lt;path:username&gt;&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryUser</span>(<span class="params">username</span>):</span><br><span class="line">    <span class="built_in">print</span>(username)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(username))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;welcome &#x27;</span> + username</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/user/&lt;username&gt;/all&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryAllUsers</span>(<span class="params">username</span>):</span><br><span class="line">    <span class="built_in">print</span>(username)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(username))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;welcome &#x27;</span> + username</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/user/queryById/&lt;int:num&gt;&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryUserById</span>(<span class="params">num</span>):</span><br><span class="line">    <span class="built_in">print</span>(num)</span><br><span class="line">    <span class="built_in">print</span>(<span class="built_in">type</span>(num))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;查询成功&#x27;</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/test&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">test</span>():</span><br><span class="line">    <span class="built_in">print</span>(url_for(<span class="string">&#x27;queryUser&#x27;</span>, username=<span class="string">&#x27;jay-chou&#x27;</span>))</span><br><span class="line">    <span class="built_in">print</span>(url_for(<span class="string">&#x27;queryAllUsers&#x27;</span>, username=<span class="string">&#x27;jay-chou&#x27;</span>))</span><br><span class="line">    <span class="built_in">print</span>(url_for(<span class="string">&#x27;queryUserById&#x27;</span>, num=<span class="string">&#x27;666&#x27;</span>))</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;OK&#x27;</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line">    </span><br></pre></td></tr></table></figure>

<p>打印结果：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">/user/jay-chou</span><br><span class="line">/user/jay-chou/all</span><br><span class="line">/user/queryById/666</span><br></pre></td></tr></table></figure>

<h2 id="redirect重定向"><a href="#redirect重定向" class="headerlink" title="redirect重定向"></a>redirect重定向</h2><p>使用redirect方法，前端对执行重定向</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request, redirect</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/redirect&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">my_redirect</span>():</span><br><span class="line">    <span class="keyword">return</span> redirect(<span class="string">&#x27;https://www.bilibili.com&#x27;</span>)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<h2 id="使用jinja2模板引擎"><a href="#使用jinja2模板引擎" class="headerlink" title="使用jinja2模板引擎"></a>使用jinja2模板引擎</h2><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, abort, render_template, request, redirect</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/index/&lt;username&gt;&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">index</span>(<span class="params">username</span>):</span><br><span class="line">    <span class="keyword">return</span> render_template(<span class="string">&#x27;index.html&#x27;</span>, username=username)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run(host=<span class="string">&#x27;0.0.0.0&#x27;</span>, port=<span class="number">80</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<figure class="highlight html"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">&lt;!DOCTYPE <span class="keyword">html</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">html</span> <span class="attr">lang</span>=<span class="string">&quot;en&quot;</span>&gt;</span></span><br><span class="line">  <span class="tag">&lt;<span class="name">head</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">meta</span> <span class="attr">charset</span>=<span class="string">&quot;UTF-8&quot;</span> /&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">meta</span> <span class="attr">http-equiv</span>=<span class="string">&quot;X-UA-Compatible&quot;</span> <span class="attr">content</span>=<span class="string">&quot;IE=edge&quot;</span> /&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">meta</span> <span class="attr">name</span>=<span class="string">&quot;viewport&quot;</span> <span class="attr">content</span>=<span class="string">&quot;width=device-width, initial-scale=1.0&quot;</span> /&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">title</span>&gt;</span>Document<span class="tag">&lt;/<span class="name">title</span>&gt;</span></span><br><span class="line">  <span class="tag">&lt;/<span class="name">head</span>&gt;</span></span><br><span class="line">  <span class="tag">&lt;<span class="name">body</span>&gt;</span></span><br><span class="line">    <span class="tag">&lt;<span class="name">h1</span>&gt;</span>welcome: &#123;&#123;username&#125;&#125;<span class="tag">&lt;/<span class="name">h1</span>&gt;</span></span><br><span class="line">  <span class="tag">&lt;/<span class="name">body</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">html</span>&gt;</span></span><br><span class="line"></span><br></pre></td></tr></table></figure>

<p>访问<a target="_blank" rel="noopener" href="http://127.0.0.1/index/jay-chou">http://127.0.0.1/index/jay-chou</a></p>
<p><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220706161252973.png" alt="image-20220706161252973"></p>
<p>可以看到，网页被渲染了出来</p>
<h2 id="连接数据库"><a href="#连接数据库" class="headerlink" title="连接数据库"></a>连接数据库</h2><h3 id="引入库"><a href="#引入库" class="headerlink" title="引入库"></a>引入库</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">pip install pymysql</span><br></pre></td></tr></table></figure>

<h3 id="规范一个数据库操作类（以MySQL为例）"><a href="#规范一个数据库操作类（以MySQL为例）" class="headerlink" title="规范一个数据库操作类（以MySQL为例）"></a>规范一个数据库操作类（以MySQL为例）</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">class</span> <span class="title class_">MysqlDb</span>():</span><br><span class="line"></span><br><span class="line">    <span class="keyword">def</span> <span class="title function_">__init__</span>(<span class="params">self, host, port, user, passwd, db</span>):</span><br><span class="line">        <span class="comment"># 建立数据库连接</span></span><br><span class="line">        self.conn = pymysql.connect(</span><br><span class="line">            host=host,</span><br><span class="line">            port=port,</span><br><span class="line">            user=user,</span><br><span class="line">            passwd=passwd,</span><br><span class="line">            db=db,</span><br><span class="line">            autocommit=<span class="literal">True</span></span><br><span class="line">        )</span><br><span class="line">        <span class="comment"># 通过 cursor() 创建游标对象，并让查询结果以字典格式输出</span></span><br><span class="line">        self.cur = self.conn.cursor(cursor=pymysql.cursors.DictCursor)</span><br><span class="line"></span><br><span class="line">    <span class="keyword">def</span> <span class="title function_">__del__</span>(<span class="params">self</span>):  <span class="comment"># 对象资源被释放时触发，在对象即将被删除时的最后操作</span></span><br><span class="line">        <span class="comment"># 关闭游标</span></span><br><span class="line">        self.cur.close()</span><br><span class="line">        <span class="comment"># 关闭数据库连接</span></span><br><span class="line">        self.conn.close()</span><br><span class="line"></span><br><span class="line">    <span class="keyword">def</span> <span class="title function_">select_db</span>(<span class="params">self, sql</span>):</span><br><span class="line">        <span class="string">&quot;&quot;&quot;查询&quot;&quot;&quot;</span></span><br><span class="line">        <span class="comment"># 检查连接是否断开，如果断开就进行重连</span></span><br><span class="line">        self.conn.ping(reconnect=<span class="literal">True</span>)</span><br><span class="line">        <span class="comment"># 使用 execute() 执行sql</span></span><br><span class="line">        self.cur.execute(sql)</span><br><span class="line">        <span class="comment"># 使用 fetchall() 获取查询结果</span></span><br><span class="line">        data = self.cur.fetchall()</span><br><span class="line">        <span class="keyword">return</span> data</span><br><span class="line"></span><br><span class="line">    <span class="keyword">def</span> <span class="title function_">execute_db</span>(<span class="params">self, sql</span>):</span><br><span class="line">        <span class="string">&quot;&quot;&quot;更新/新增/删除&quot;&quot;&quot;</span></span><br><span class="line">        <span class="keyword">try</span>:</span><br><span class="line">            <span class="comment"># 检查连接是否断开，如果断开就进行重连</span></span><br><span class="line">            self.conn.ping(reconnect=<span class="literal">True</span>)</span><br><span class="line">            <span class="comment"># 使用 execute() 执行sql</span></span><br><span class="line">            self.cur.execute(sql)</span><br><span class="line">            <span class="comment"># 提交事务</span></span><br><span class="line">            self.conn.commit()</span><br><span class="line">        <span class="keyword">except</span> Exception <span class="keyword">as</span> e:</span><br><span class="line">            <span class="built_in">print</span>(<span class="string">&quot;操作出现错误：&#123;&#125;&quot;</span>.<span class="built_in">format</span>(e))</span><br><span class="line">            <span class="comment"># 回滚所有更改</span></span><br><span class="line">            self.conn.rollback()</span><br></pre></td></tr></table></figure>

<h3 id="实例化一个全局单例"><a href="#实例化一个全局单例" class="headerlink" title="实例化一个全局单例"></a>实例化一个全局单例</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">db = MysqlDb(MYSQL_HOST, MYSQL_PORT, MYSQL_USER, MYSQL_PASSWD, MYSQL_DB)</span><br></pre></td></tr></table></figure>

<p>相关数据库配置信息自行配置</p>
<h3 id="全局使用"><a href="#全局使用" class="headerlink" title="全局使用"></a>全局使用</h3><p>在开发代码中，写好需要使用的SQL语句，调用全局单例db提供的API，执行数据库事务</p>
<p>举一个例子，首先新建一个用户表：</p>
<figure class="highlight sql"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">CREATE</span> <span class="keyword">TABLE</span> `<span class="keyword">user</span>` (</span><br><span class="line">  `id` <span class="type">int</span> <span class="keyword">NOT</span> <span class="keyword">NULL</span> AUTO_INCREMENT,</span><br><span class="line">  `nick_name` <span class="type">varchar</span>(<span class="number">255</span>) <span class="keyword">NOT</span> <span class="keyword">NULL</span>,</span><br><span class="line">  `age` <span class="type">int</span> <span class="keyword">NOT</span> <span class="keyword">NULL</span>,</span><br><span class="line">  <span class="keyword">PRIMARY</span> KEY (`id`)</span><br><span class="line">) ENGINE<span class="operator">=</span>InnoDB AUTO_INCREMENT<span class="operator">=</span><span class="number">3</span> <span class="keyword">DEFAULT</span> CHARSET<span class="operator">=</span>utf8mb4 <span class="keyword">COLLATE</span><span class="operator">=</span>utf8mb4_0900_ai_ci;</span><br></pre></td></tr></table></figure>

<p>插入几个数据</p>
<figure class="highlight sql"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">INSERT</span> <span class="keyword">INTO</span> `<span class="keyword">user</span>` <span class="keyword">VALUES</span> (<span class="number">1</span>, <span class="string">&#x27;小明&#x27;</span>, <span class="number">5</span>);</span><br><span class="line"><span class="keyword">INSERT</span> <span class="keyword">INTO</span> `<span class="keyword">user</span>` <span class="keyword">VALUES</span> (<span class="number">2</span>, <span class="string">&#x27;小红&#x27;</span>, <span class="number">18</span>);</span><br></pre></td></tr></table></figure>

<p>这里我们获取用户表中所有的用户信息：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">sql = <span class="string">&#x27;select * from user&#x27;</span></span><br><span class="line">data = db.select_db(sql)</span><br><span class="line"><span class="built_in">print</span>(data)</span><br></pre></td></tr></table></figure>

<p>打印结果：</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">[&#123;<span class="string">&#x27;id&#x27;</span>: 1, <span class="string">&#x27;nick_name&#x27;</span>: <span class="string">&#x27;小明&#x27;</span>, <span class="string">&#x27;age&#x27;</span>: 5&#125;, &#123;<span class="string">&#x27;id&#x27;</span>: 2, <span class="string">&#x27;nick_name&#x27;</span>: <span class="string">&#x27;小红&#x27;</span>, <span class="string">&#x27;age&#x27;</span>: 18&#125;]</span><br></pre></td></tr></table></figure>

<p>笔者也浅尝过Flask的ORM框架，但说实话，并没有简单操作，甚至有些复杂……因此，这里就不做阐述了</p>
<h2 id="自定义装饰器"><a href="#自定义装饰器" class="headerlink" title="自定义装饰器"></a>自定义装饰器</h2><h3 id="导包"><a href="#导包" class="headerlink" title="导包"></a>导包</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> functools <span class="keyword">import</span> wraps</span><br></pre></td></tr></table></figure>

<h3 id="自定义处理逻辑"><a href="#自定义处理逻辑" class="headerlink" title="自定义处理逻辑"></a>自定义处理逻辑</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, abort</span><br><span class="line"><span class="keyword">from</span> functools <span class="keyword">import</span> wraps</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">has_powercode</span>(<span class="params">powercode</span>):</span><br><span class="line">    <span class="keyword">def</span> <span class="title function_">decorator</span>(<span class="params">f</span>):</span><br><span class="line"><span class="meta">        @wraps(<span class="params">f</span>)</span></span><br><span class="line">        <span class="keyword">def</span> <span class="title function_">decorated_function</span>(<span class="params">*args, **kwargs</span>):</span><br><span class="line">            <span class="string">&quot;&quot;&quot;处理逻辑（简化处理）&quot;&quot;&quot;</span></span><br><span class="line">            <span class="keyword">if</span> powercode != <span class="string">&#x27;user:add&#x27;</span>:</span><br><span class="line">                abort(<span class="number">403</span>)</span><br><span class="line">            <span class="keyword">return</span> f(*args, **kwargs)</span><br><span class="line">        <span class="keyword">return</span> decorated_function</span><br><span class="line">    <span class="keyword">return</span> decorator</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/api/user/add&#x27;</span>, methods=[<span class="string">&#x27;GET&#x27;</span>]</span>)</span></span><br><span class="line"><span class="meta">@has_powercode(<span class="params"><span class="string">&#x27;user:delete&#x27;</span></span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">add_user</span>():</span><br><span class="line">    <span class="keyword">return</span> <span class="string">&#x27;success&#x27;</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">&#x27;__main__&#x27;</span>:</span><br><span class="line">    app.run()</span><br><span class="line"></span><br></pre></td></tr></table></figure>

<p>网页简单测试一下：</p>
<p><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220708224340905.png" alt="image-20220708224340905"></p>
<p>很遗憾，在装饰器因权限不足，出发了abort(403)，程序就不会结束该函数，不会继续执行被该装饰器所修饰的函数了</p>
<h3 id="能做些什么"><a href="#能做些什么" class="headerlink" title="能做些什么"></a>能做些什么</h3><p>我们可以用来做<code>Authentication</code>和<code>Authorization</code>(可恶，想起了无聊的搬砖生活……)</p>
<p>通过装饰器，自定义个性化的身份验证和鉴权逻辑，从而满足系统的安全保障</p>
<h2 id="配置Swagger文档"><a href="#配置Swagger文档" class="headerlink" title="配置Swagger文档"></a>配置Swagger文档</h2><p>作为一个开发工程师，写好一个接口文档在团队协作中非常重要，Flask也集成了Swagger文档，我们来看看怎么使用</p>
<h3 id="引入库-1"><a href="#引入库-1" class="headerlink" title="引入库"></a>引入库</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">pip install flasgger</span><br></pre></td></tr></table></figure>

<h3 id="配置相关信息"><a href="#配置相关信息" class="headerlink" title="配置相关信息"></a>配置相关信息</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flasgger <span class="keyword">import</span> Swagger</span><br><span class="line"></span><br><span class="line">swagger_config = Swagger.DEFAULT_CONFIG  <span class="comment"># Swagger通过配置信息渲染SwaggerUI展示信息</span></span><br><span class="line">swagger_config[<span class="string">&#x27;title&#x27;</span>] = TITLE  <span class="comment"># 接口文档标题</span></span><br><span class="line">swagger_config[<span class="string">&#x27;version&#x27;</span>] = VERSION  <span class="comment"># 版本号</span></span><br><span class="line">swagger_config[<span class="string">&#x27;termsOfService&#x27;</span>] = TERMSOFSERVICE  <span class="comment"># 条文说明</span></span><br><span class="line">swagger_config[<span class="string">&#x27;specs&#x27;</span>][<span class="number">0</span>][<span class="string">&#x27;route&#x27;</span>] = ROUTE  <span class="comment"># 接口集合路由</span></span><br><span class="line">swagger_config[<span class="string">&#x27;description&#x27;</span>] = DESCRIPTION  <span class="comment"># 描述</span></span><br><span class="line"></span><br><span class="line">Swagger(app, config=swagger_config)</span><br></pre></td></tr></table></figure>

<h3 id="对应每一个接口填写描述信息"><a href="#对应每一个接口填写描述信息" class="headerlink" title="对应每一个接口填写描述信息"></a>对应每一个接口填写描述信息</h3><p>例如，我们这里有一个通过用户名称获取用户信息的接口：</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@app.route(<span class="params"><span class="string">&#x27;/api/user/queryByName/&lt;string:username&gt;&#x27;</span>, methods=[<span class="string">&quot;GET&quot;</span>]</span>)</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">queryUserByName</span>(<span class="params">username</span>):</span><br><span class="line">    <span class="string">&quot;&quot;&quot;</span></span><br><span class="line"><span class="string">    通过名称获取用户信息</span></span><br><span class="line"><span class="string">    ---</span></span><br><span class="line"><span class="string">    tags:</span></span><br><span class="line"><span class="string">      - 用户接口</span></span><br><span class="line"><span class="string">    parameters:</span></span><br><span class="line"><span class="string">      - name: username</span></span><br><span class="line"><span class="string">        in: path</span></span><br><span class="line"><span class="string">        type: string</span></span><br><span class="line"><span class="string">        required: true</span></span><br><span class="line"><span class="string">        description: 用户名称</span></span><br><span class="line"><span class="string">    responses:</span></span><br><span class="line"><span class="string">      1001:</span></span><br><span class="line"><span class="string">        description: 不可传入空</span></span><br><span class="line"><span class="string">      1004:</span></span><br><span class="line"><span class="string">        description: 查不到该用户</span></span><br><span class="line"><span class="string">      0:</span></span><br><span class="line"><span class="string">        description: 查询成功</span></span><br><span class="line"><span class="string">    &quot;&quot;&quot;</span></span><br><span class="line">    <span class="keyword">return</span> user.queryByName(username)</span><br></pre></td></tr></table></figure>

<p>相关描述信息以yaml的形式写在了方法下面的注释代码块里面（个人觉得很魔性）</p>
<p>flasgger包里会有程序来阅读这些配置，并将描述信息渲染在页面上</p>
<h3 id="真实的样貌"><a href="#真实的样貌" class="headerlink" title="真实的样貌"></a>真实的样貌</h3><p><img src="https://0-bit.oss-cn-beijing.aliyuncs.com/image-20220708222333577.png" alt="image-20220708222333577"></p>
<h2 id="开启跨域"><a href="#开启跨域" class="headerlink" title="开启跨域"></a>开启跨域</h2><h3 id="引入库-2"><a href="#引入库-2" class="headerlink" title="引入库"></a>引入库</h3><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">pip install flask-cors</span><br></pre></td></tr></table></figure>

<h3 id="常用配置"><a href="#常用配置" class="headerlink" title="常用配置"></a>常用配置</h3><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request</span><br><span class="line"><span class="keyword">from</span> flask_cors <span class="keyword">import</span> CORS</span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line">CORS(app, supports_credentials=<span class="literal">True</span>)</span><br></pre></td></tr></table></figure>


  </div>
</article>


    <div class="blog-post-comments">
        <div id="utterances_thread">
            <noscript>Please enable JavaScript to view the comments.</noscript>
        </div>
    </div>


        
          <div id="footer-post-container">
  <div id="footer-post">

    <div id="nav-footer" style="display: none">
      <ul>
         
          <li><a href="/">Home</a></li>
         
          <li><a href="/about/">About</a></li>
         
          <li><a href="/archives/">Articles</a></li>
         
          <li><a href="/categories/">Category</a></li>
         
          <li><a href="/search/">Search</a></li>
        
      </ul>
    </div>

    <div id="toc-footer" style="display: none">
      <ol class="toc"><li class="toc-item toc-level-1"><a class="toc-link" href="#Python-Web-Flask%E6%A1%86%E6%9E%B6"><span class="toc-number">1.</span> <span class="toc-text">Python Web Flask框架</span></a><ol class="toc-child"><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BB%8B%E7%BB%8D"><span class="toc-number">1.1.</span> <span class="toc-text">介绍</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%AE%89%E8%A3%85"><span class="toc-number">1.2.</span> <span class="toc-text">安装</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%9F%A5%E7%9C%8B%E4%BB%8B%E7%BB%8D%E5%92%8C%E7%89%88%E6%9C%AC"><span class="toc-number">1.2.1.</span> <span class="toc-text">查看介绍和版本</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#Hello-World"><span class="toc-number">1.3.</span> <span class="toc-text">Hello World</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E9%A1%B9%E7%9B%AE%E7%BB%93%E6%9E%84"><span class="toc-number">1.3.1.</span> <span class="toc-text">项目结构</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%AC%AC%E4%B8%80%E4%B8%AA%E7%A8%8B%E5%BA%8F"><span class="toc-number">1.3.2.</span> <span class="toc-text">第一个程序</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E4%BF%AE%E6%94%B9Flask%E9%85%8D%E7%BD%AE"><span class="toc-number">1.3.3.</span> <span class="toc-text">修改Flask配置</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Debug%E6%A8%A1%E5%BC%8F"><span class="toc-number">1.3.4.</span> <span class="toc-text">Debug模式</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%BB%91%E5%AE%9AIP%E5%92%8C%E7%AB%AF%E5%8F%A3"><span class="toc-number">1.3.5.</span> <span class="toc-text">绑定IP和端口</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%8E%B7%E5%8F%96URL%E5%8F%82%E6%95%B0"><span class="toc-number">1.4.</span> <span class="toc-text">获取URL参数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%8E%B7%E5%8F%96POST%E5%8F%82%E6%95%B0"><span class="toc-number">1.5.</span> <span class="toc-text">获取POST参数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%A7%A3%E6%9E%90JSON"><span class="toc-number">1.6.</span> <span class="toc-text">解析JSON</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%BF%94%E5%9B%9E%E4%BD%93%E8%87%AA%E5%AE%9A%E4%B9%89"><span class="toc-number">1.6.1.</span> <span class="toc-text">返回体自定义</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%96%B9%E5%BC%8F%E4%B8%80"><span class="toc-number">1.6.1.1.</span> <span class="toc-text">方式一</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%96%B9%E5%BC%8F%E4%BA%8C"><span class="toc-number">1.6.1.2.</span> <span class="toc-text">方式二</span></a></li></ol></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%B8%8A%E4%BC%A0%E6%96%87%E4%BB%B6"><span class="toc-number">1.7.</span> <span class="toc-text">上传文件</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#RESTFUL%E9%A3%8E%E6%A0%BCURL"><span class="toc-number">1.8.</span> <span class="toc-text">RESTFUL风格URL</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%88%9D%E6%8E%A2"><span class="toc-number">1.8.1.</span> <span class="toc-text">初探</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%B1%BB%E5%9E%8B%E8%BD%AC%E6%8D%A2"><span class="toc-number">1.8.2.</span> <span class="toc-text">类型转换</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E4%BD%BF%E7%94%A8url-for"><span class="toc-number">1.8.3.</span> <span class="toc-text">使用url_for</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#redirect%E9%87%8D%E5%AE%9A%E5%90%91"><span class="toc-number">1.9.</span> <span class="toc-text">redirect重定向</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BD%BF%E7%94%A8jinja2%E6%A8%A1%E6%9D%BF%E5%BC%95%E6%93%8E"><span class="toc-number">1.10.</span> <span class="toc-text">使用jinja2模板引擎</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%BF%9E%E6%8E%A5%E6%95%B0%E6%8D%AE%E5%BA%93"><span class="toc-number">1.11.</span> <span class="toc-text">连接数据库</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E5%85%A5%E5%BA%93"><span class="toc-number">1.11.1.</span> <span class="toc-text">引入库</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%A7%84%E8%8C%83%E4%B8%80%E4%B8%AA%E6%95%B0%E6%8D%AE%E5%BA%93%E6%93%8D%E4%BD%9C%E7%B1%BB%EF%BC%88%E4%BB%A5MySQL%E4%B8%BA%E4%BE%8B%EF%BC%89"><span class="toc-number">1.11.2.</span> <span class="toc-text">规范一个数据库操作类（以MySQL为例）</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AE%9E%E4%BE%8B%E5%8C%96%E4%B8%80%E4%B8%AA%E5%85%A8%E5%B1%80%E5%8D%95%E4%BE%8B"><span class="toc-number">1.11.3.</span> <span class="toc-text">实例化一个全局单例</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%85%A8%E5%B1%80%E4%BD%BF%E7%94%A8"><span class="toc-number">1.11.4.</span> <span class="toc-text">全局使用</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E8%87%AA%E5%AE%9A%E4%B9%89%E8%A3%85%E9%A5%B0%E5%99%A8"><span class="toc-number">1.12.</span> <span class="toc-text">自定义装饰器</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AF%BC%E5%8C%85"><span class="toc-number">1.12.1.</span> <span class="toc-text">导包</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%87%AA%E5%AE%9A%E4%B9%89%E5%A4%84%E7%90%86%E9%80%BB%E8%BE%91"><span class="toc-number">1.12.2.</span> <span class="toc-text">自定义处理逻辑</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E8%83%BD%E5%81%9A%E4%BA%9B%E4%BB%80%E4%B9%88"><span class="toc-number">1.12.3.</span> <span class="toc-text">能做些什么</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E9%85%8D%E7%BD%AESwagger%E6%96%87%E6%A1%A3"><span class="toc-number">1.13.</span> <span class="toc-text">配置Swagger文档</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E5%85%A5%E5%BA%93-1"><span class="toc-number">1.13.1.</span> <span class="toc-text">引入库</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E9%85%8D%E7%BD%AE%E7%9B%B8%E5%85%B3%E4%BF%A1%E6%81%AF"><span class="toc-number">1.13.2.</span> <span class="toc-text">配置相关信息</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AF%B9%E5%BA%94%E6%AF%8F%E4%B8%80%E4%B8%AA%E6%8E%A5%E5%8F%A3%E5%A1%AB%E5%86%99%E6%8F%8F%E8%BF%B0%E4%BF%A1%E6%81%AF"><span class="toc-number">1.13.3.</span> <span class="toc-text">对应每一个接口填写描述信息</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E7%9C%9F%E5%AE%9E%E7%9A%84%E6%A0%B7%E8%B2%8C"><span class="toc-number">1.13.4.</span> <span class="toc-text">真实的样貌</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%BC%80%E5%90%AF%E8%B7%A8%E5%9F%9F"><span class="toc-number">1.14.</span> <span class="toc-text">开启跨域</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E5%85%A5%E5%BA%93-2"><span class="toc-number">1.14.1.</span> <span class="toc-text">引入库</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%B8%B8%E7%94%A8%E9%85%8D%E7%BD%AE"><span class="toc-number">1.14.2.</span> <span class="toc-text">常用配置</span></a></li></ol></li></ol></li></ol>
    </div>

    <div id="share-footer" style="display: none">
      <ul>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.facebook.com/sharer.php?u=https://cheung0-bit.github.io/ec225509277f/"><i class="fab fa-facebook fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://twitter.com/share?url=https://cheung0-bit.github.io/ec225509277f/&text=Flask框架快速入门"><i class="fab fa-twitter fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.linkedin.com/shareArticle?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-linkedin fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://pinterest.com/pin/create/bookmarklet/?url=https://cheung0-bit.github.io/ec225509277f/&is_video=false&description=Flask框架快速入门"><i class="fab fa-pinterest fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" href="mailto:?subject=Flask框架快速入门&body=Check out this article: https://cheung0-bit.github.io/ec225509277f/"><i class="fas fa-envelope fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://getpocket.com/save?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-get-pocket fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://reddit.com/submit?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-reddit fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.stumbleupon.com/submit?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-stumbleupon fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://digg.com/submit?url=https://cheung0-bit.github.io/ec225509277f/&title=Flask框架快速入门"><i class="fab fa-digg fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="http://www.tumblr.com/share/link?url=https://cheung0-bit.github.io/ec225509277f/&name=Flask框架快速入门&description="><i class="fab fa-tumblr fa-lg" aria-hidden="true"></i></a></li>
  <li><a class="icon" target="_blank" rel="noopener" href="https://news.ycombinator.com/submitlink?u=https://cheung0-bit.github.io/ec225509277f/&t=Flask框架快速入门"><i class="fab fa-hacker-news fa-lg" aria-hidden="true"></i></a></li>
</ul>

    </div>

    <div id="actions-footer">
        <a id="menu" class="icon" href="#" onclick="$('#nav-footer').toggle();return false;"><i class="fas fa-bars fa-lg" aria-hidden="true"></i> Menu</a>
        <a id="toc" class="icon" href="#" onclick="$('#toc-footer').toggle();return false;"><i class="fas fa-list fa-lg" aria-hidden="true"></i> TOC</a>
        <a id="share" class="icon" href="#" onclick="$('#share-footer').toggle();return false;"><i class="fas fa-share-alt fa-lg" aria-hidden="true"></i> Share</a>
        <a id="top" style="display:none" class="icon" href="#" onclick="$('html, body').animate({ scrollTop: 0 }, 'fast');"><i class="fas fa-chevron-up fa-lg" aria-hidden="true"></i> Top</a>
    </div>

  </div>
</div>

        
        <footer id="footer">
  <div class="footer-left">
    Copyright &copy;
      
        
          2022-2024
            <a target="_blank" rel="noopener" href="https://beian.miit.gov.cn/">
              苏ICP备2022044873号
            </a>
  </div>
  <div class="footer-right">
    <nav>
      <ul>
        
          <!--
       -->
          <li><a href="/">
              Home
            </a></li>
          <!--
     -->
          
          <!--
       -->
          <li><a href="/about/">
              About
            </a></li>
          <!--
     -->
          
          <!--
       -->
          <li><a href="/archives/">
              Articles
            </a></li>
          <!--
     -->
          
          <!--
       -->
          <li><a href="/categories/">
              Category
            </a></li>
          <!--
     -->
          
          <!--
       -->
          <li><a href="/search/">
              Search
            </a></li>
          <!--
     -->
          
      </ul>
    </nav>
  </div>
</footer>
    </div>
    <!-- styles -->


 
  <link
    rel="preload"
    href="/lib/font-awesome/css/all.min.css"
    as="style"
    onload="this.onload=null;this.rel='stylesheet'"
  />
  <noscript
    ><link
      rel="stylesheet"
      href="/lib/font-awesome/css/all.min.css"
  /></noscript>



    <!-- jquery -->
 
  
<script src="/lib/jquery/jquery.min.js"></script>





<!-- clipboard -->

   
    
<script src="/lib/clipboard/clipboard.min.js"></script>

  
  <script type="text/javascript">
  $(function() {
    // copy-btn HTML
    var btn = "<span class=\"btn-copy tooltipped tooltipped-sw\" aria-label=\"Copy to clipboard!\">";
    btn += '<i class="far fa-clone"></i>';
    btn += '</span>'; 
    // mount it!
    $(".highlight table").before(btn);
    var clip = new ClipboardJS('.btn-copy', {
      text: function(trigger) {
        return Array.from(trigger.nextElementSibling.querySelectorAll('.code')).reduce((str,it)=>str+it.innerText+'\n','')
      }
    });
    clip.on('success', function(e) {
      e.trigger.setAttribute('aria-label', "Copied!");
      e.clearSelection();
    })
  })
  </script>


<script src="/js/main.js"></script>

<!-- search -->

<!-- Google Analytics -->

<!-- Baidu Analytics -->

  <script type="text/javascript">
        var _hmt = _hmt || [];
        (function() {
          var hm = document.createElement("script");
          hm.src = "https://hm.baidu.com/hm.js?4484a4a33014b59670c470a6e15a66db";
          var s = document.getElementsByTagName("script")[0];
          s.parentNode.insertBefore(hm, s);
        })();
        </script>

<!-- Cloudflare Analytics -->

<!-- Umami Analytics -->

<!-- Disqus Comments -->

<!-- utterances Comments -->

    <script type="text/javascript">
      var utterances_repo = 'Cheung0-bit/blog-package';
      var utterances_issue_term = 'title';
      var utterances_label = 'Comment';
      var utterances_theme = 'github-dark';

      (function(){
          var script = document.createElement('script');

          script.src = 'https://utteranc.es/client.js';
          script.setAttribute('repo', utterances_repo);
          script.setAttribute('issue-term', 'pathname');
          script.setAttribute('label', utterances_label);
          script.setAttribute('theme', utterances_theme);
          script.setAttribute('crossorigin', 'anonymous');
          script.async = true;
          (document.getElementById('utterances_thread')).appendChild(script);
      }());
  </script>

</body>
</html>
